package com.example.springboot_manage.service.impl;

import com.alibaba.druid.util.StringUtils;
import com.example.springboot_manage.model.Account;
import com.example.springboot_manage.model.Admin;
import com.example.springboot_manage.model.AdminExample;
import com.example.springboot_manage.repository.AccountRepository;
import com.example.springboot_manage.repository.AdminMapper;
import com.example.springboot_manage.service.AccountService;
import com.example.springboot_manage.util.JsonUtil;
import com.example.springboot_manage.util.Md5Util;
import com.example.springboot_manage.util.UUIDUtil;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.data.redis.core.RedisTemplate;
import org.springframework.data.redis.core.ValueOperations;
import org.springframework.stereotype.Service;
import org.springframework.util.CollectionUtils;

import javax.servlet.http.HttpSession;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.concurrent.TimeUnit;

@Service
public class AccountServiceImpl implements AccountService {

    @Autowired
    private AccountRepository accountRepository;
    @Autowired
    private AdminMapper adminMapper;

    private static Logger logger = LoggerFactory.getLogger(AccountServiceImpl.class);

    @Autowired
    private RedisTemplate<String, String> redisTemplate;
    @Value("${user.ticket}")
    private String userTicket;
    @Value("${admin.info}")
    private String adminInfo;


    @Override
    public Account findByUsername(String username) {
        Account account = accountRepository.findByUsername(username);
        return account;
    }

    @Override
    public Map<String, Object> loginVerify(String userName, String passWord) {
        Map<String,Object> map = new HashMap<String,Object>();
        Account account = accountRepository.findByUsername(userName);
        if (account != null){
            if (passWord.equals(account.getPassword())){
                map.put("code",1);
                map.put("msg","");
                if (account.getRoot()==1){
                    map.put("root",1);
                }
                else{
                    map.put("root",0);
                }
            }else {
                map.put("code",0);
                map.put("msg","密码不正确");
            }
        }else{
            map.put("code",0);
            map.put("msg","账号不存在");
        }
        return map;
    }

    @Override
    public String updateImages(String newFileName, HttpSession session) {
        Account account = (Account) session.getAttribute("loginInfo");
        String uid = "/images/"+newFileName;
        String oldFileName = (String) accountRepository.findById(account.getId());
        String[] area = oldFileName.split("/");
        String oldFileName1 = area[area.length-1];
        Account account1 = new Account();
        account1.setId(account.getId());
        account1.setHeadPortrait(uid);
        int flag = accountRepository.upload(account1);
        if (flag==1){
            account.setHeadPortrait(uid);
            session.setAttribute("loginInfo",account);
            return oldFileName1;
        }else{
            return null;
        }

    }

    /**
     * 登录认证返回票据
     * @param admin
     * @return
     */
    @Override
    public String login(Admin admin) {
        if (StringUtils.isEmpty(admin.getUserName().trim())){
            logger.error("用户名为空");
            return null;
        }
        if (StringUtils.isEmpty(admin.getPassword().trim())){
            logger.error("密码为空");
            return null;
        }
        AdminExample example = new AdminExample();
        example.createCriteria().andUserNameEqualTo(admin.getUserName());
        List<Admin> list = adminMapper.selectByExample(example);
        if (CollectionUtils.isEmpty(list)){
            logger.error("用户名或密码不正确！");
            return null;
        }
        Admin a = list.get(0);
        if (!a.getPassword().equals(Md5Util.getMd5WithSalt(admin.getPassword(),a.getEcSalt()))){
            logger.error("用户名或密码不正确！");
            return null;
        }
        //用户名密码正确,生成票据ticket存入redis
        ValueOperations<String,String> valueOperations = redisTemplate.opsForValue();
        String ticket = UUIDUtil.getUUID();
        valueOperations.set(userTicket + ":" + ticket, JsonUtil.object2JsonStr(a),
                30, TimeUnit.MINUTES);
        return ticket;
    }

    /**
     * 查找AdminId
     * @param admin
     * @return
     */
    @Override
    public Integer findAdminId(Admin admin) {
        AdminExample example = new AdminExample();
        example.createCriteria().andUserNameEqualTo(admin.getUserName());
        List<Admin> list = adminMapper.selectByExample(example);
        Admin a = list.get(0);
        return a!=null? Integer.valueOf(a.getAdminId()):0;
    }

    /**
     * 查找用户信息
     * @param id
     * @return
     */
    @Override
    public Account findLoginInfo(Integer id,String ticket) {
        ValueOperations<String,String> valueOperations = redisTemplate.opsForValue();
        String adminJson = valueOperations.get(adminInfo+":"+ticket);
        if (!StringUtils.isEmpty(adminJson)){
            Account account = JsonUtil.jsonStr2Object(adminJson,Account.class);
            return account;
        }
        Account account = accountRepository.findByAdminId(id);
        valueOperations.set(adminInfo+":"+ticket,JsonUtil.object2JsonStr(account));
        return account;
    }

    /**
     * 更改个人信息
     * @param account
     * @return
     */
    @Override
    public synchronized Account updatePersonInfo(Account account,String ticket) {
        ValueOperations<String,String> valueOperations = redisTemplate.opsForValue();
        valueOperations.set(adminInfo+":"+ticket,JsonUtil.object2JsonStr(account));
        String adminInfoJson = valueOperations.get(adminInfo+":"+ticket);
        Account account1 = JsonUtil.jsonStr2Object(adminInfoJson,Account.class);
        return account1;
    }

    /**
     * 验证ticket返回用户信息
     * @param ticket
     * @return
     */
    @Override
    public Admin validate(String ticket){
        if (StringUtils.isEmpty(ticket)){
            logger.error("票据信息不存在！");
            return null;
        }
        ValueOperations<String ,String> valueOperations = redisTemplate.opsForValue();
        String adminJson = valueOperations.get(userTicket + ":" + ticket);
        if (StringUtils.isEmpty(adminJson)){
            logger.error("票据对应的用户信息不存在！");
            return null;
        }
        return JsonUtil.jsonStr2Object(adminJson,Admin.class);

    }

    /**
     * 用户退出
     * @param ticket
     */
    @Override
    public void logout(String ticket) {
        //退出时保存用户信息
        ValueOperations<String,String> valueOperations = redisTemplate.opsForValue();
        String adminJson = valueOperations.get(adminInfo+":"+ticket);
        if (!StringUtils.isEmpty(adminJson)){
            Account account = JsonUtil.jsonStr2Object(adminJson,Account.class);
            int result = accountRepository.update(account);
            if (result==0){
                logger.error("用户信息保存到数据库失败！"+"::"+ticket+"::"+account);
            }
        }
        redisTemplate.delete(userTicket + ":" + ticket);
        redisTemplate.delete(adminInfo+":"+ticket);
    }


}
